package com.itheima.reggie.webfilter;

import com.alibaba.fastjson.JSON;
import com.itheima.reggie.common.R;
import com.itheima.reggie.common.ThreadData;
import lombok.extern.slf4j.Slf4j;
import org.springframework.util.AntPathMatcher;

import javax.servlet.*;
import javax.servlet.annotation.WebFilter;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

/**
 * 登录检查过滤器
 * 访问静态页面时放行
 * 访问动态页面时检查是否登录
 * <p>
 * A. 获取本次请求的URI
 * B. 判断本次请求, 是否需要登录, 才可以访问
 * C. 如果不需要，则直接放行
 * D. 判断登录状态，如果已登录，则直接放行
 * E. 如果未登录, 则返回未登录结果
 */
@Slf4j

//TODO 需要在引导类(配置的启动类)上, 加上Servlet组件扫描的注解, 来扫描过滤器配置的@WebFilter注解， 扫描上之后， 过滤器在运行时就生效了。
@WebFilter(filterName = "loginCheckFilter", urlPatterns = "/*")
public class LoginCheckFilter implements Filter {
    //路径匹配器，支持通配符
    //TODO  没讲的知识点,好像是可以将字符串路径和带有通配符的数组路径进行比较  √
    public static final AntPathMatcher PATH_MATCHER = new AntPathMatcher();


    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain)
            throws IOException, ServletException {
        //* A. 获取本次请求的URI
        HttpServletRequest request = (HttpServletRequest) servletRequest;
        HttpServletResponse response = (HttpServletResponse) servletResponse;
        String uri = request.getRequestURI();
        log.info("拦截到的请求{}", uri);

        // * B. 判断本次请求, 是否需要登录, 才可以访问
        String[] urls = {"/employee/login",
                "/employee/logout",
                "/backend/**",
                "/front/**",
                "/user/login",
                "/user/sendMsg"
        }; //静态页面直接放行


        for (String url : urls) {
            //TODO 注意两个参数的位置,参数①是带通配符(匹配规则),参数②是正常的字符串
            boolean match = PATH_MATCHER.match(url, uri);   //match 比较后的结果
            if (match) {
                // C * 路径相等代表访问的是静态资源 --> 放行
                log.info("本次请求{},不需要拦截", uri);
                //TODO 用 filterChain掉方法放行
                filterChain.doFilter(request, response);
                //结束过滤器
                return;
            }
        }

        //* D. 判断登录状态，如果已登录，则直接放行
        if (request.getSession().getAttribute("employee") != null) {

            log.info("管理员已经登陆 , id是: " + request.getSession().getAttribute("employee"));
            Long id = (Long) request.getSession().getAttribute("employee");
            //存入线程池
            ThreadData.setId(id);
            filterChain.doFilter(request, response);     //放行
            return;
        }

        // D.2 判断用户登录状态
        if (request.getSession().getAttribute("user") != null) {

            log.info("用户已经登陆 , id是: " + request.getSession().getAttribute("user"));
            Long id = (Long) request.getSession().getAttribute("user");
            //存入线程池
            ThreadData.setId(id);
            filterChain.doFilter(request, response);     //放行
            return;
        }

        //走到这 就只剩下最后一个可能了, 用户未登录 给前段响应一下
        // * E. 如果未登录, 则返回未登录结果
        response.getWriter().print(JSON.toJSONString(R.error("NOTLOGIN")));

    }


}
